package com.jichangxiu.system.service.impl;

import cn.hutool.core.util.ObjectUtil;
import com.github.yulichang.base.MPJBaseServiceImpl;
import com.jichangxiu.common.utils.ConvertUtils;
import com.jichangxiu.framework.utils.SecurityUtils;
import com.jichangxiu.system.entity.bo.SysPostBo;
import com.jichangxiu.system.entity.bo.SysPostDeptBo;
import com.jichangxiu.system.entity.dto.edit.EditSysPost;
import com.jichangxiu.system.entity.po.SysPostDept;
import com.jichangxiu.system.mapper.SysPostDeptMapper;
import com.jichangxiu.system.service.SysPostDeptService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;

/**
 * SysPostDeptServiceImpl:
 *
 * @author JiChangXiu
 * @create 2024-06-28 13:44:34
 */
@Slf4j
@Service
public class SysPostDeptServiceImpl extends MPJBaseServiceImpl<SysPostDeptMapper, SysPostDept> implements SysPostDeptService {

    /**
     * 增加 / 修改 / 删除 岗位部门关联列表
     *
     * @param editSysPost        系统岗位
     * @param sysPostDeptBoList 岗位部门关联对象列表
     * @return 是否成功
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean addOrDelOrEdit(EditSysPost editSysPost, List<SysPostDeptBo> sysPostDeptBoList) {
        SysPostBo sysPostBo = ConvertUtils.convert(editSysPost, SysPostBo.class);
        // 角色和自定义数据权限关联关系
        boolean b1 = true;
        boolean b2 = true;
        // 前端传来的角色部门关联关系
        List<String> deptIdList = editSysPost.getDeptIdList();
        // 本次要新增的角色部门关联关系
        List<SysPostDept> addSysPostDeptList = new ArrayList<>();
        // 本次要删除的角色部门关联关系
        List<String> deleteRoleDeptIds = new ArrayList<>();
        if (ObjectUtil.isEmpty(deptIdList) && ObjectUtil.isEmpty(sysPostDeptBoList)) {
            // 如果两者都是空的则什么都不做
            log.info("本次无需操作");
        } else if (ObjectUtil.isNotEmpty(deptIdList) && ObjectUtil.isNotEmpty(sysPostDeptBoList)) {
            // 如果两者都不是空的
            for (String deptId : deptIdList) {
                // 当前部门在数据库中是否存在，这里的判断值 默认不存在
                boolean flag = false;
                for (SysPostDeptBo sysPostDeptBo : sysPostDeptBoList) {
                    if (deptId.equals(sysPostDeptBo.getDeptId())) {
                        // 代表当前部门在数据库中已经存在
                        flag = true;
                        break;
                    }
                }
                // 到上个循环结束还不存在，则证明当前部门在数据库中不存在，需要录入数据库中
                if (!flag)
                    addSysPostDeptList.add(SysPostDept.builder().postId(sysPostBo.getId()).deptId(deptId).tenantId(SecurityUtils.getTenantId()).build());
            }
            // 循环数据库中的值在页面传来的 List 中是否存在，如果不存在，则代表当前值被用户删除
            for (SysPostDeptBo sysPostDeptBo : sysPostDeptBoList) {
                // 默认不存在
                boolean flag = false;
                for (String deptId : deptIdList) {
                    if (sysPostDeptBo.getDeptId().equals(deptId)) {
                        // 存在
                        flag = true;
                        break;
                    }
                }
                if (!flag)
                    // 一直到上个循环结束，还是不存在，则证明当前数据库值已被用户删除
                    deleteRoleDeptIds.add(sysPostDeptBo.getId());
            }
        } else if (ObjectUtil.isEmpty(deptIdList) && ObjectUtil.isNotEmpty(sysPostDeptBoList)) {
            // 页面传过来是空的，则需要把数据库中所有已经存在的数据全部删除
            sysPostDeptBoList.forEach(sysPostDeptBo -> deleteRoleDeptIds.add(sysPostDeptBo.getId()));
        } else if (ObjectUtil.isNotEmpty(deptIdList) && ObjectUtil.isEmpty(sysPostDeptBoList)) {
            // 如果页面传过来的不是空的，而数据库中尚未保存数据，则将页面传过来的全部保存
            deptIdList.forEach(deptId -> addSysPostDeptList.add(SysPostDept.builder().postId(sysPostBo.getId()).deptId(deptId).tenantId(SecurityUtils.getTenantId()).build()));
        }
        if (ObjectUtil.isNotEmpty(addSysPostDeptList))
            b1 = saveBatch(addSysPostDeptList);
        if (ObjectUtil.isNotEmpty(deleteRoleDeptIds))
            b2 = removeBatchByIds(deleteRoleDeptIds);
        return b1 && b2;
    }

}